<!-- MyComponent.vue -->
<template>
  <view class="container">
    <uv-form labelPosition="left" :model="model1" :rules="rules" ref="form">
      <uv-form-item label="数值" prop="datum.val" borderBottom>
        <uv-input v-model="model1.datum.val" border="none"></uv-input>
      </uv-form-item>
      <uv-form-item label="单位" prop="datum.unit" @click="showUnitSelect">
        <uv-input
          v-model="model1.datum.unit"
          disabled
          disabledColor="#ffffff"
          placeholder="请选择单位"
          border="none"
        ></uv-input>
        <template v-slot:right>
          <uv-icon name="arrow-right"></uv-icon>
        </template>
      </uv-form-item>
    </uv-form>
    <uv-divider text="转换结果"></uv-divider>
    <uv-form labelPosition="left" :model="modelResult" ref="convertResult">
      <uv-form-item
        v-for="(item, key) in modelResult"
        :key="key"
        :label="unitNames[key]"
        :prop="key"
        borderBottom
      >
        <uv-input v-model="modelResult[key]" disabled border="none"></uv-input>
      </uv-form-item>
    </uv-form>
    <uv-action-sheet
      ref="uSelect"
      :actions="actions"
      title="请选择单位"
      description=""
      @select="unitSelect"
    ></uv-action-sheet>
  </view>
</template>

<script>
export default {
  name: "WeightConverter",
  data() {
    return {
      unitNames: {
        g: "克",
        kg: "千克",
        mg: "毫克",
        oz: "盎司",
        lb: "磅",
        ton: "吨",
        liang: "两",
        jin: "斤",
        zhu: "铢",
        jun: "均",
        shi: "石"
      },
      model1: {
        datum: {
          val: "1",
          unit: "克"
        }
      },
      modelResult: {
        g: 0,
        kg: 0,
        mg: 0,
        oz: 0,
        lb: 0,
        ton: 0,
        liang: 0,
        jin: 0,
        zhu: 0,
        jun: 0,
        shi: 0
      },
      actions: [
        { name: "克" },
        { name: "千克" },
        { name: "毫克" },
        { name: "盎司" },
        { name: "磅" },
        { name: "吨" },
        { name: "两" },
        { name: "斤" },
        { name: "铢" },
        { name: "均" },
        { name: "石" }
      ],
      rules: {
        "datum.val": {
          type: "number",
          required: true,
          message: "请填写数字"
        }
      },
      radio: "",
      switchVal: false
    }
  },
  watch: {
    "model1.datum.val": function (newVal) {
      const find = Object.keys(this.unitNames).find(
        k => this.unitNames[k] == this.model1.datum.unit
      )
      this.convertAll(newVal, find)
    },
    "model1.datum.unit": function (newVal) {
      const find = Object.keys(this.unitNames).find(k => this.unitNames[k] == newVal)
      this.convertAll(this.model1.datum.val, find)
    }
  },
  methods: {
    showUnitSelect() {
      this.$refs.uSelect.open()
      this.hideKeyboard()
    },
    unitSelect(e) {
      this.model1.datum.unit = e.name
    },
    convertAll(value, fromUnit) {
      for (let unitNamesKey in this.unitNames) {
        this.modelResult[unitNamesKey] = this.convertWeight(value, fromUnit, unitNamesKey)
      }
    },
    convertWeight(value, fromUnit, toUnit) {
      // 公制单位间转换
      const metricToMetric = {
        g: { mg: 1000, kg: 0.001 },
        kg: { g: 1000, mg: 1e6 },
        mg: { g: 0.001, kg: 1e-6 }
      }

      // 英制单位间转换
      const imperialToImperial = {
        oz: { lb: 0.0625, ton: 0.00003125 },
        lb: { oz: 16, ton: 0.00078125 },
        ton: { oz: 32000, lb: 2000 }
      }

      // 公制与英制单位转换
      const metricToImperial = {
        g: { oz: 0.035274, lb: 0.00220462, ton: 0.00000220462 },
        kg: { oz: 35.274, lb: 2.20462, ton: 0.00220462 },
        ton: { oz: 35274, lb: 2204.62, g: 1e6 }
      }

      const imperialToMetric = {
        oz: { g: 28.3495, kg: 0.0283495, ton: 0.0000283495 },
        lb: { g: 453.592, kg: 0.453592, ton: 0.000453592 },
        ton: { g: 907185, kg: 907.185, oz: 32000 }
      }

      // 中国古代重量单位转换到公制
      const traditionalToMetric = {
        liang: { g: 50, kg: 0.05 },
        jin: { g: 500, kg: 0.5 },
        zhu: { g: 0.666667, kg: 0.000666667 }, // 假设1两=24铢
        jun: { g: 5000, kg: 5 }, // 假设1均为10斤
        shi: { g: 50000, kg: 50 } // 假设1石=100斤
      }

      // 公制转中国古代重量单位
      const metricToTraditional = {
        g: { liang: 0.02, jin: 0.002, zhu: 0.000333333, jun: 0.00002, shi: 0.000002 },
        kg: { liang: 2, jin: 2, zhu: 0.333333, jun: 0.02, shi: 0.002 }
      }

      let result

      if (fromUnit in metricToMetric && toUnit in metricToMetric) {
        result = value * metricToMetric[fromUnit][toUnit]
      } else if (fromUnit in imperialToImperial && toUnit in imperialToImperial) {
        result = value * imperialToImperial[fromUnit][toUnit]
      } else if (fromUnit in metricToImperial && toUnit in imperialToMetric) {
        result = value * metricToImperial[fromUnit][toUnit]
      } else if (fromUnit in imperialToMetric && toUnit in metricToImperial) {
        result = value * imperialToMetric[fromUnit][toUnit]
      } else if (fromUnit in traditionalToMetric && toUnit in metricToMetric) {
        result = value * traditionalToMetric[fromUnit][toUnit]
      } else if (fromUnit in metricToTraditional && toUnit in traditionalToMetric) {
        result = value * metricToTraditional[fromUnit][toUnit]
      } else {
        throw new Error("Unsupported conversion between " + fromUnit + " and " + toUnit)
      }

      return result
    },
    hideKeyboard() {
      uni.hideKeyboard()
    }
  }
}
</script>

<style scoped>
.my-component {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  padding: 20px;
  background-color: #f0f0f0;
}

.container {
  padding: 0 15px;
}

button {
  margin-top: 10px;
  padding: 5px 10px;
  border-radius: 5px;
  background-color: #007aff;
  color: white;
}
</style>
